﻿from fastapi import APIRouter, HTTPException, Depends
from fastapi.responses import JSONResponse
from qcloud_cos import CosS3Client, CosServiceError
from src.dependencies.cos_client import get_cos_client
from src.config import settings
from src.utils.logger import logger
from datetime import datetime, timedelta
import urllib.parse

router = APIRouter()

def generate_preview_url(file_key: str, cos_client: CosS3Client) -> str:
    """
    生成带签名的文档预览 URL
    """
    try:
        # 生成签名 URL，有效期 1 小时
        url = cos_client.get_presigned_url(
            Method='GET',
            Bucket=settings.COS_BUCKET_NAME,
            Key=file_key,
            Expired=3600,  # 1小时有效期
            Params={
                'ci-process': 'doc-preview',
                'dstType': 'html',
                'copyable': '1'
            }
        )
        return url
    except Exception as e:
        logger.error(f"生成预览 URL 失败: {str(e)}")
        raise

def generate_download_url(file_key: str, cos_client: CosS3Client) -> str:
    """
    生成带签名的文件下载 URL
    """
    try:
        # 生成签名 URL，有效期 1 小时
        url = cos_client.get_presigned_url(
            Method='GET',
            Bucket=settings.COS_BUCKET_NAME,
            Key=file_key,
            Expired=3600  # 1小时有效期
        )
        return url
    except Exception as e:
        logger.error(f"生成下载 URL 失败: {str(e)}")
        raise
@router.get("/list-files",
            summary="获取 COS 桶中的文件列表",
            response_description="文件列表，包含文件名、URL 等信息")
async def list_files(
    prefix: str = "filled_excel/",
    cos_client: CosS3Client = Depends(get_cos_client)
):
    """
    获取 COS 桶中指定前缀的文件列表。
    默认获取 filled_excel/ 目录下的文件。
    """
    try:
        logger.info(f"正在获取文件列表，前缀: {prefix}")
        response = cos_client.list_objects(
            Bucket=settings.COS_BUCKET_NAME,
            Prefix=prefix,
            MaxKeys=1000
        )

        files = []
        if 'Contents' in response:
            for item in response['Contents']:
                # 获取文件名（不包含路径）
                file_name = item['Key'].split('/')[-1]
                # 过滤掉不是文件的对象（如目录本身，通常 key 以 / 结尾或 name 为空）
                if not file_name or item['Key'].endswith('/'):
                    continue

                # 处理最后修改时间
                last_modified = item.get('LastModified', '')
                if isinstance(last_modified, str):
                    try:
                        # 尝试解析 COS 返回的时间字符串
                        last_modified = datetime.strptime(last_modified, '%Y-%m-%dT%H:%M:%S.%fZ')
                    except ValueError:
                        # 如果解析失败，使用当前时间
                        last_modified = datetime.now()
                
                # 生成带签名的预览和下载 URL
                preview_url = generate_preview_url(item['Key'], cos_client)
                download_url = generate_download_url(item['Key'], cos_client)
                
                files.append({
                    "name": file_name,
                    "key": item['Key'],
                    "url": download_url, 
                    "objectUrl": f"https://{settings.COS_BUCKET_NAME}.cos.{settings.COS_REGION}.myqcloud.com/{item['Key']}",  # 使用带签名的下载 URL
                    "size": item['Size'],
                    "last_modified": last_modified.isoformat() if isinstance(last_modified, datetime) else last_modified,
                    "preview_url": preview_url,
                    "bucket": settings.COS_BUCKET_NAME,
                    "region": settings.COS_REGION,
                    "app_id": settings.COS_APP_ID
                })

        logger.info(f"成功获取文件列表，共 {len(files)} 个文件")
        return JSONResponse(content={
            "files": files,
            "total": len(files)
        })

    except Exception as e:
        error_msg = f"获取文件列表失败: {str(e)}"
        logger.error(error_msg)
        raise HTTPException(status_code=500, detail=error_msg)

@router.get("/doc-preview-status",
            summary="查询文档预览开通状态",
            response_description="文档预览功能状态信息")
async def get_doc_preview_status(
    cos_client: CosS3Client = Depends(get_cos_client)
):
    """
    查询存储桶的文档预览功能开通状态。
    """
    try:
        # 使用 ci_get_doc_bucket 方法查询文档预览状态
        response = cos_client.ci_get_doc_bucket(
            Regions=settings.COS_REGION,
            BucketNames=settings.COS_BUCKET_NAME,
            PageSize=1,
            PageNumber=1
        )
        
        logger.info(f"文档预览状态查询结果: {response}")
        
        # 检查是否有 DocBucketList 且不为空
        has_doc_bucket = bool(response.get('DocBucketList'))
        
        return JSONResponse(content={
            "status": "enabled" if has_doc_bucket else "disabled",
            "details": response
        })

    except CosServiceError as e:
        error_msg = f"查询文档预览状态失败: {str(e)}"
        logger.error(error_msg)
        raise HTTPException(status_code=500, detail=error_msg)
    except Exception as e:
        error_msg = f"查询文档预览状态失败: {str(e)}"
        logger.error(error_msg)
        raise HTTPException(status_code=500, detail=error_msg)
@router.get("/get_object_url",
            summary="获取对象访问链接",
            response_description="对象的访问 URL")
async def get_object_url(
    key: str,
    cos_client: CosS3Client = Depends(get_cos_client)
):

    try:
        response = cos_client.get_object_url(
            Bucket=settings.COS_BUCKET_NAME,
            Key=key
        )
        logger.info(f"获取对象 URL 结果: {response}")
        return JSONResponse(content={
            "object_url": response
        })
    except Exception as e:
        error_msg = f"获取对象 URL 失败: {str(e)}"
        logger.error(error_msg)
        raise HTTPException(status_code=500, detail=error_msg)

